from rest_framework import viewsets, status, generics
from rest_framework.decorators import action
from rest_framework.response import Response
from rest_framework.permissions import IsAuthenticated, AllowAny
from .models import Banner, Category, Goods, Cart
from .serializers import (
    BannerSerializer,
    CategorySerializer,
    CategoryWithSubSerializer,
    GoodsSerializer,
    GoodsListSerializer,
    CartSerializer
)


class IndexView(generics.GenericAPIView):
    """首页数据API"""
    permission_classes = [AllowAny]

    def get(self, request):
        # 获取轮播图数据
        banners = Banner.objects.all()[:5]
        banner_serializer = BannerSerializer(banners, many=True)

        # 获取分类数据
        categories = Category.objects.filter(parent=None)[:8]
        category_serializer = CategorySerializer(categories, many=True)

        # 获取爆款商品数据
        hot_goods = Goods.objects.filter(is_hot=True)[:6]
        hot_goods_serializer = GoodsSerializer(hot_goods, many=True)

        return Response({
            'banners': banner_serializer.data,
            'categories': category_serializer.data,
            'hot_goods': hot_goods_serializer.data
        })


class CategoryListView(generics.ListAPIView):
    """分类列表API"""
    permission_classes = [AllowAny]
    queryset = Category.objects.filter(parent=None)
    serializer_class = CategoryWithSubSerializer


class GoodsListView(generics.ListAPIView):
    """商品列表API"""
    permission_classes = [AllowAny]
    serializer_class = GoodsListSerializer

    def get_queryset(self):
        queryset = Goods.objects.all()

        # 筛选分类
        category_id = self.request.query_params.get('category_id')
        if category_id:
            # 获取该分类及其所有子分类
            category = Category.objects.get(id=category_id)
            category_ids = [category.id] + list(category.sub_categories.values_list('id', flat=True))
            queryset = queryset.filter(category__id__in=category_ids)

        # 排序
        sort = self.request.query_params.get('sort')
        if sort == 'price_asc':
            queryset = queryset.order_by('current_price')
        elif sort == 'price_desc':
            queryset = queryset.order_by('-current_price')
        elif sort == 'sales':
            queryset = queryset.order_by('-sales')
        else:
            queryset = queryset.order_by('-created_time')

        return queryset


class CartViewSet(viewsets.ModelViewSet):
    """购物车视图集"""
    permission_classes = [IsAuthenticated]
    serializer_class = CartSerializer

    def get_queryset(self):
        return Cart.objects.filter(user=self.request.user).select_related('goods')

    @action(detail=False, methods=['get'])
    def count(self, request):
        """获取购物车商品数量"""
        count = Cart.objects.filter(user=request.user).count()
        return Response({'count': count})

    @action(detail=False, methods=['post'])
    def select(self, request):
        """选择/取消选择购物车商品"""
        goods_id = request.data.get('goods_id')
        selected = request.data.get('selected', True)

        if not goods_id:
            return Response({'error': 'goods_id is required'}, status=status.HTTP_400_BAD_REQUEST)

        try:
            cart_item = Cart.objects.get(user=request.user, goods_id=goods_id)
            cart_item.selected = selected
            cart_item.save()
            return Response({'success': True})
        except Cart.DoesNotExist:
            return Response({'error': 'Cart item not found'}, status=status.HTTP_404_NOT_FOUND)

    @action(detail=False, methods=['post'])
    def update_num(self, request):
        """更新购物车商品数量"""
        goods_id = request.data.get('goods_id')
        num = request.data.get('num')

        if not goods_id or not num:
            return Response({'error': 'goods_id and num are required'}, status=status.HTTP_400_BAD_REQUEST)

        try:
            num = int(num)
            if num <= 0:
                return Response({'error': 'num must be positive'}, status=status.HTTP_400_BAD_REQUEST)

            cart_item = Cart.objects.get(user=request.user, goods_id=goods_id)
            cart_item.num = num
            cart_item.save()
            return Response({'success': True})
        except ValueError:
            return Response({'error': 'num must be integer'}, status=status.HTTP_400_BAD_REQUEST)
        except Cart.DoesNotExist:
            return Response({'error': 'Cart item not found'}, status=status.HTTP_404_NOT_FOUND)